<?php

/**
 * Contains a class to define a Store object to describe a store's properties.
 *
 * PHP Version 5
 *
 * @category BuyLocal
 * @package  BuyLocal
 * @author   Kevin Fodness <kevin.fodness@gmail.com>
 * @author   Mike Pennisi <mpennisi@andrew.cmu.edu>
 * @author   Aaron Ryden <aryden@gmail.com>
 * @license  http://opensource.org/licenses/gpl-license.php GNU Public License
 * @link     http://code.google.com/p/buylocalopensourcerensselaer/
 */

/** @uses encode For strict HTML compliant output. */
require_once 'function_encode.php';
 
/**
 * A class to define a Store object to describe a store's properties.
 *
 * @category BuyLocal
 * @package  BuyLocal
 * @author   Kevin Fodness <kevin.fodness@gmail.com>
 * @author   Mike Pennisi <mpennisi@andrew.cmu.edu>
 * @author   Aaron Ryden <aryden@gmail.com>
 * @license  http://opensource.org/licenses/gpl-license.php GNU Public License
 * @link     http://code.google.com/p/buylocalopensourcerensselaer/
 */ 
class Store
{
    /**
     * The database unique identifier for this store.
     *
     * @access public
     * @var int       Corresponds to stores.id
     */
    public $id;
    
    /**
     * The name of the store (e.g., Bob's Hot Dog Shack).
     *
     * @access public
     * @var string    Corresponds to stores.name
     */
    public $name;
    
    /**
     * The description of the store.
     *
     * @access public
     * @var string    Corresponds to stores.description
     */
    public $description;
    
    /**
     * The UNIX timestamp of the date that the store was added.
     *
     * @access public
     * @var int       Corresponds to stores.dateadded
     */
    public $dateAdded;
    
    /**
     * The street address of the store.
     *
     * @access public
     * @var string    Corresponds to stores.address
     */
    public $address;
    
    /**
     * The city in which the store is located.
     *
     * @access public
     * @var string    Corresponds to stores.city
     */
    public $city;
    
    /**
     * The state in which the store is located.
     *
     * @access public
     * @var string    Corresponds to stores.state
     */
    public $state;
    
    /**
     * The ZIP code in which the store is located.
     *
     * @access public
     * @var string    Corresponds to stores.zip
     */
    public $zip;
    
    /**
     * The country in which the store is located.
     *
     * @access public
     * @var string    Corresponds to stores.country
     */
    public $country;
    
    /**
     * The latitude of the store's geographic location.
     *
     * @access public
     * @var float     Corresponds to stores.latitude
     */
    public $latitude;
    
    /**
     * The longitude of the store's geographic location.
     *
     * @access public
     * @var float     Corresponds to stores.longitude
     */
    public $longitude;
    
    /**
     * An array of Category objects describing categories this store is in.
     *
     * @access public
     * @var array     Corresponds to storecategories
     */
    public $categories;

    /**
     * An array of Phone objects describing the phone numbers of the store.
     *
     * @access public
     * @var array     Corresponds to storephones
     */
    public $phoneNumbers;
    
    /**
     * An array of Fax objects describing the fax numbers of the store.
     *
     * @access public
     * @var array     Corresponds to storefaxes
     */
    public $faxNumbers;
    
    /**
     * An array of Email objects describing the email addresses of the store.
     *
     * @access public
     * @var array     Corresponds to storeemails
     */
    public $emailAddresses;
    
    /**
     * The path to the image for this store, or to the null image.
     *
     * @access public
     * @var string    Corresponds to storeimages
     */
    public $imagePath;

    /**
     * The distance between the store and the user's home zip code.
     *
     * @access public
     * @var float
     */
    public $distance;

    /**
     * The events associated with the store.
     *
     * @access public
     * @var array
     */
    public $events;
    
    /**
     * Constructor function.  Populates variables based on parameters.
     *
     * @param int    $id             The unique ID for the store.
     * @param string $name           The name of the store.
     * @param string $description    The description of the store.
     * @param int    $dateAdded      The date and time the store was added.
     * @param string $address        The street address of the store.
     * @param string $city           The city the store is located in.
     * @param string $state          The state the store is located in.
     * @param string $zip            The zip code of the store.
     * @param string $country        The country the store is located in.
     * @param float  $latitude       The store's latitude.
     * @param float  $longitude      The store's longitude.
     * @param array  $categories     The categories this store belongs to.
     * @param array  $phoneNumbers   The store's phone numbers.
     * @param array  $faxNumbers     The store's fax numbers.
     * @param array  $emailAddresses The store's email addresses.
     * @param string $imagePath      The path to the store's image.
     * @param float  $distance       The distance between store and user's ZIP.
     * @param array  $events         The events associated with the store.
     *
     * @access public
     * @return null
     */
    public function __construct($id = null, $name = null, $description = null,
        $dateAdded = null, $address = null, $city = null, $state = null,
        $zip = null, $country = null, $latitude = null, $longitude = null,
        $categories = array(), $phoneNumbers = array(), 
        $faxNumbers = array(), $emailAddresses = array(), $imagePath = null,
        $distance = null, $events = array()
    ) {
        $this->id             = $id;
        $this->name           = $name;
        $this->description    = $description;
        $this->dateAdded      = $dateAdded;
        $this->address        = $address;
        $this->city           = $city;
        $this->state          = $state;
        $this->zip            = $zip;
        $this->country        = $country;
        $this->latitude       = $latitude;
        $this->longitude      = $longitude;
        $this->categories     = $categories;
        $this->phoneNumbers   = $phoneNumbers;
        $this->faxNumbers     = $faxNumbers;
        $this->emailAddresses = $emailAddresses;
        $this->imagePath      = $imagePath;
        $this->distance       = $distance;
        $this->events         = $events;
    }

    /**
     * The clone function. Is called via the PHP5 'clone' keyword.
     * Since the 'clone' keyword automatically does a shallow copy of variables,
     * this code finishes the work and does a deep copy.
     *
     * @access public
     * @return null
     */
    public function __clone()
    {
        foreach ($this as $key => $val) {
            if (is_object($val) || is_array($val)) {
                $this->{$key} = unserialize(serialize($val));
            }
        }
    }
    
    /**
     * Function to print a store as a list item for display on the home page
     * and in store search results.
     *
     * @param bool $userIsOwner whether or not to print the Edit link.
     * @param bool $printAll    Whether or not to print all of the store info.
     *
     * @access public
     * @return null
     */
    public function printListItem($userIsOwner = false, $printAll = false)
    {
        /** Compiles the categories into a string. */
        $categories = '';
        foreach ($this->categories as $category) {
            $categories .= "\n" . '     <a href="' . RELATIVE_PATH
                . 'browse.php?categoryid=' . $category->id . '">'
                . encode($category->name) . '</a>,';
        }
        $categories = substr($categories, 0, strlen($categories) - 1);
        
        /** Prints the list item. */
        echo '  <li>', "\n",
            '   <img src="', $this->imagePath, '" alt="Picture of ',
            encode($this->name), '" />', "\n",
            '   <div>', "\n",
            '    <h2>';
        if (!$printAll) {
            echo '<a href="', RELATIVE_PATH, 'stores.php?storeid=',
            $this->id, '">', encode($this->name), '</a>';
        } else {
            echo encode($this->name);
        }
        echo '</h2>', "\n",
            '    <address>', "\n",
            '     ', encode($this->address), '<br/>', "\n",
            '     ', encode($this->city), ', ', encode($this->state), ' ',
            $this->zip, '<br/>', "\n",
            '     ', encode($this->country), "\n",
            '    </address>', "\n",
            '    <p>', encode(substr($this->description, 0, 500)), '</p>', "\n";
        if ($this->distance != null) {
            echo '    <p><strong>Distance:</strong> ', 
                number_format($this->distance, 2), ' ', D_DISTANCE, '</p>',
            "\n";
        }
        if ($printAll) {
            $this->_printPhoneNumbers();
            $this->_printFaxNumbers();
            $this->_printEmailAddresses();
        }
        echo '    <p>', "\n",
            '     <strong>Categories:</strong>', $categories, "\n",
            '    </p>', "\n";
        if ($printAll) {
            $this->_printEvents();
        }

        if ($userIsOwner) {
            echo '   <br/><a href="', RELATIVE_PATH, 'user/edit_store.php?storeid=',
                $this->id, '">Edit Store</a>', "\n",
                '   - <a href="', RELATIVE_PATH, 'admin/stores.php?action=delete',
                '&storeid=', $this->id, '" onclick="return confirm(\'Are you sure',
                ' you wish to delete this store?\');">Delete Store</a>', "\n";
        }
        echo '   </div>', "\n",
            '  </li>', "\n";
    }
    
    /**
     * Function to print the list item with all information present.
     *
     * @param bool $userIsOwner whether or not to print the Edit link.
     *
     * @access public
     * @return null
     */
    function printListItemFull($userIsOwner = false)
    {
        $this->printListItem($userIsOwner, true);
    }
    
    /**
     * Function to print a list of phone numbers for this store.
     *
     * @access private
     * @return null
     */
    private function _printPhoneNumbers()
    {
        if (count($this->phoneNumbers) == 0) {
            return null;
        }
        echo '    <p><strong>Phone Numbers:</strong></p>', "\n",
            '    <ul>', "\n";
        foreach ($this->phoneNumbers as $phone) {
            echo '     <li><strong>', $phone->description, ':</strong> ',
                $phone->number, '</li>', "\n";
        }
        echo '    </ul>', "\n";
    }
    
    /**
     * Function to print a list of fax numbers for this store.
     *
     * @access private
     * @return null
     */
    private function _printFaxNumbers()
    {
        if (count($this->faxNumbers) == 0) {
            return null;
        }
        echo '    <p><strong>Fax Numbers:</strong></p>', "\n",
            '    <ul>', "\n";
        foreach ($this->faxNumbers as $fax) {
            echo '     <li><strong>', $fax->description, ':</strong> ',
                $fax->number, '</li>', "\n";
        }
        echo '    </ul>', "\n";
    }
    
    /**
     * Function to print a list of email addresses for this store.
     *
     * @access private
     * @return null
     */
    private function _printEmailAddresses()
    {
        if (count($this->emailAddresses) == 0) {
            return null;
        }
        echo '    <p><strong>Email Addresses:</strong></p>', "\n",
            '    <ul>', "\n";
        foreach ($this->emailAddresses as $email) {
            echo '     <li><strong>', $email->description, ':</strong> ',
                '<a href="mailto:', $email->address, '">',
                $email->address, '</a></li>', "\n";
        }
        echo '    </ul>', "\n";
    }

    /**
     * Function to print a list of events for this store.
     *
     * @access private
     * @return null
     */
    private function _printEvents()
    {
        if (count($this->events) == 0) {
            return null;
        }
        echo '    <p><strong>Events:</strong></p>', "\n",
            '    <ul>', "\n";
        foreach ($this->events as $event) {            
            echo '     <li><a href="', RELATIVE_PATH, 'event.php?eventid=',
                $event->id, '"><strong>', $event->name, '</strong></a> - ',
                strftime('%D %I:%M%p', $event->startTime),
                '</li>', "\n";
        }
        echo '    </ul>', "\n";
    }
}

?>